#include <sys/types.h>

#ifdef HAVE_CONFIG_H
#include "config.h"
#endif

#include <sys/time.h>
#include <sys/param.h>
#include <sys/stat.h>
#include <sys/queue.h>
#include <stdlib.h>
#include <stdio.h>
#include <string.h>
#include <err.h>
#include <fcntl.h>
#include <unistd.h>
#include <assert.h>
#include <errno.h>

#include <event.h>
#include <evhttp.h>

#include "amproxy.gen.h"
#include "utils.h"
#include "log.h"

ssize_t atomicio(ssize_t (*f) (), int fd, void *_s, size_t n);

extern int debug;


struct dangerq danger;
static int danger_init;

//初始化队列
static void
init_danger(void)
{
	if (!danger_init) {
		danger_init = 1;
		TAILQ_INIT(&danger);
	}
}


//初始化记录文件		
int
log_init(const char *filename)
{
	int fd;

	init_danger();

	fd = open(filename, O_RDWR|O_APPEND|O_CREAT, S_IRUSR|S_IWUSR|S_IRGRP);
	if (fd == -1)
		return (-1);

	return (fd);
}

void
log_close(int fd)
{
	close(fd);
}

struct dangerousload *
log_dl_from_request(struct evhttp_request *req)
{
	struct dangerousload *dl = dangerousload_new();
	struct timeval tv;

	assert(dl != NULL);

	gettimeofday(&tv, NULL);
	EVTAG_ASSIGN(dl, time_in_seconds, tv.tv_sec);
	EVTAG_ASSIGN(dl, parent_url,
	    evhttp_find_header(req->input_headers, "Referer"));
	EVTAG_ASSIGN(dl, dangerous_url, req->uri);

	return (dl);
}


/*
 * logs information only about the parent and the dangerous URL.
 */

void
log_dangerous_request(int log_fd, struct evhttp_request *req)
{
	struct dangerous_container *dc =
	    malloc(sizeof(struct dangerous_container));
	struct dangerousload *dl = log_dl_from_request(req);
	struct evbuffer *data = evbuffer_new();

	assert(data != NULL);
	assert(dc != NULL);

	evtag_marshal_dangerousload(data, DANGEROUS_TAG, dl);



	atomicio(write, log_fd, EVBUFFER_DATA(data), EVBUFFER_LENGTH(data));
	fsync(log_fd);
	evbuffer_free(data);

	dc->dl = dl;
	TAILQ_INSERT_HEAD(&danger, dc, next);
}






